package com.xbj.cloud.test.juc;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * @author: 观雾
 * @create: 2024-09-15
 * @description:
 **/

public class ThreadDemo1 {
    public static void main(String[] args) {
        Share share = new Share();
        //syncTest(share);
        System.out.println("======================");
        lockTest(share);
        List<Object> list = Collections.synchronizedList(new ArrayList<>());
        List<Object> list1 = new CopyOnWriteArrayList<>();

    }
    public static void syncTest(Share share){
        new Thread(new Runnable() {
            @Override
            public void run() {
                for (int i = 0; i < 6; i++) {
                    try {
                        share.syncAdd();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }
        },"A").start();

        new Thread(()->{
            for (int i = 0; i < 6; i++) {
                try {
                    share.syncSub();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        },"B").start();
    }

    public static void lockTest(Share share){
        new Thread(()->{
            for (int i = 0; i < 6; i++) {
                try {
                    share.lockAdd();
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        },"C").start();

        new Thread(()->{
            for (int i = 0; i < 6; i++) {
                try {
                    share.lockSub();
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        },"D").start();

    }
}


class Share{

    private int num = 1;

    public synchronized void syncAdd() throws InterruptedException {
        //System.out.println("name="+Thread.currentThread().getName() +"进入");
        while (num != 0){
            this.wait();
        }
        num++;
        System.out.println("name="+Thread.currentThread().getName() +",num="+num);
        this.notifyAll();
    }

    public synchronized void syncSub() throws InterruptedException {
        //System.out.println("name="+Thread.currentThread().getName()+",进入" );

        while (num != 1){
            this.wait();
        }
        num--;
        System.out.println("name="+Thread.currentThread().getName()+",num="+num );
        this.notifyAll();
    }

    private Lock lock = new ReentrantLock();
    private Condition condition = lock.newCondition();

    public void lockAdd () {
        //System.out.println("name="+Thread.currentThread().getName()+",进入" );

        //上锁
        lock.lock();
        try {
            while (num != 0){
                condition.await();
            }
            num++;
            System.out.println("name="+Thread.currentThread().getName() +",num="+num);
            condition.signalAll();
        } catch (InterruptedException e) {
            e.printStackTrace();
        } finally {
            //释放锁
            lock.unlock();
        }
    }

    public void lockSub(){
        //System.out.println("name="+Thread.currentThread().getName()+",进入" );

        lock.lock();
        try {
            while (num != 1){
                condition.await();
            }
            num--;
            System.out.println("name="+Thread.currentThread().getName()+",num="+num );
            condition.signalAll();
        }catch (Exception e){

        }finally {
            lock.unlock();
        }
    }
}
